/*   1:    */ package org.intellij.plugins.relaxNG.model.descriptors;
/*   2:    */ 
/*   3:    */

import com.intellij.openapi.editor.Document;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.Key;
import com.intellij.openapi.util.Pair;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.psi.*;
import com.intellij.psi.impl.source.tree.TreeUtil;
import com.intellij.psi.util.CachedValueProvider.Result;
import com.intellij.psi.util.CachedValuesManager;
import com.intellij.psi.util.ParameterizedCachedValue;
import com.intellij.psi.util.ParameterizedCachedValueProvider;
import com.intellij.psi.util.PsiTreeUtil;
import com.intellij.psi.xml.XmlAttribute;
import com.intellij.psi.xml.XmlTag;
import com.intellij.util.ArrayUtil;
import com.intellij.util.containers.HashMap;
import com.intellij.xml.XmlAttributeDescriptor;
import com.intellij.xml.XmlElementDescriptor;
import com.intellij.xml.XmlElementsGroup;
import com.intellij.xml.XmlNSDescriptor;
import org.intellij.plugins.relaxNG.compact.RncElementTypes;
import org.intellij.plugins.relaxNG.compact.RncFileType;
import org.intellij.plugins.relaxNG.validation.RngSchemaValidator;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.Nullable;
import org.kohsuke.rngom.digested.*;
import org.kohsuke.rngom.nc.NameClass;
import org.kohsuke.rngom.nc.NameClassVisitor;
import org.xml.sax.Locator;

import javax.xml.namespace.QName;
import java.util.*;

/*   4:    */
/*   5:    */
/*   6:    */
/*   7:    */
/*   8:    */
/*   9:    */
/*  10:    */
/*  11:    */
/*  12:    */
/*  13:    */
/*  14:    */
/*  15:    */
/*  16:    */
/*  17:    */
/*  18:    */
/*  19:    */
/*  20:    */
/*  21:    */
/*  22:    */
/*  23:    */
/*  24:    */
/*  25:    */
/*  26:    */
/*  27:    */
/*  28:    */
/*  29:    */
/*  30:    */
/*  31:    */
/*  32:    */
/*  33:    */
/*  34:    */
/*  35:    */
/*  36:    */
/*  37:    */
/*  38:    */
/*  39:    */
/*  40:    */
/*  41:    */
/*  42:    */
/*  43:    */
/*  44:    */
/*  45:    */
/*  46:    */
/*  47:    */
/*  48:    */ 
/*  49:    */ public class RngElementDescriptor
/*  50:    */   implements XmlElementDescriptor
/*  51:    */ {
/*  52: 50 */   private static final Key<ParameterizedCachedValue<XmlElementDescriptor, RngElementDescriptor>> a = Key.create("DESCR");
/*  53: 51 */   private static final Key<ParameterizedCachedValue<XmlAttributeDescriptor[], RngElementDescriptor>> b = Key.create("ATTRS");
/*  54: 53 */   protected static final XmlElementDescriptor NULL = null;
/*  55:    */   private final DElementPattern c;
/*  56:    */   protected final RngNsDescriptor myNsDescriptor;
/*  57:    */   private volatile SmartPsiElementPointer<? extends PsiElement> d;
/*  58:    */   
/*  59:    */   RngElementDescriptor(RngNsDescriptor paramRngNsDescriptor, DElementPattern paramDElementPattern)
/*  60:    */   {
/*  61: 61 */     this.myNsDescriptor = paramRngNsDescriptor;
/*  62: 62 */     this.c = paramDElementPattern;
/*  63:    */   }
/*  64:    */   
/*  65:    */   public String getQualifiedName()
/*  66:    */   {
/*  67: 66 */     QName localQName = a();
/*  68: 67 */     return localQName != null ? a(localQName, "") : "#unknown";
/*  69:    */   }
/*  70:    */   
/*  71:    */   public String getDefaultName()
/*  72:    */   {
/*  73: 71 */     return getName();
/*  74:    */   }
/*  75:    */   
/*  76:    */   public XmlElementDescriptor[] getElementsDescriptors(XmlTag paramXmlTag)
/*  77:    */   {
/*  78: 75 */     if (paramXmlTag == null) {
/*  79: 76 */       return EMPTY_ARRAY;
/*  80:    */     }
/*  81: 82 */     XmlElementDescriptor localXmlElementDescriptor = this.myNsDescriptor.getElementDescriptor(paramXmlTag);
/*  82:    */     DElementPattern localDElementPattern;
/*  83: 83 */     if ((localXmlElementDescriptor instanceof RngElementDescriptor))
/*  84:    */     {
/*  85: 84 */       localObject = ((RngElementDescriptor)localXmlElementDescriptor).c;
/*  86: 85 */       localDElementPattern = localObject != null ? localObject : this.c;
/*  87:    */     }
/*  88:    */     else
/*  89:    */     {
/*  90: 87 */       localDElementPattern = this.c;
/*  91:    */     }
/*  92: 90 */     Object localObject = ChildElementFinder.find(2, localDElementPattern);
/*  93: 91 */     return this.myNsDescriptor.convertElementDescriptors((List)localObject);
/*  94:    */   }
/*  95:    */   
/*  96:    */   protected XmlElementDescriptor findElementDescriptor(XmlTag paramXmlTag)
/*  97:    */   {
/*  98: 95 */     List localList = ChildElementFinder.find(2, this.c);
/*  99: 96 */     XmlElementDescriptor localXmlElementDescriptor = this.myNsDescriptor.findDescriptor(paramXmlTag, localList);
/* 100: 97 */     return localXmlElementDescriptor == null ? NULL : localXmlElementDescriptor;
/* 101:    */   }
/* 102:    */   
/* 103:    */   public final XmlElementDescriptor getElementDescriptor(XmlTag paramXmlTag)
/* 104:    */   {
/* 105:101 */     return getElementDescriptor(paramXmlTag, null);
/* 106:    */   }
/* 107:    */   
/* 108:    */   public final XmlElementDescriptor getElementDescriptor(final XmlTag paramXmlTag1, XmlTag paramXmlTag2)
/* 109:    */   {
/* 110:105 */     XmlElementDescriptor localXmlElementDescriptor = (XmlElementDescriptor)a(paramXmlTag1, this, a, new ParameterizedCachedValueProvider()
/* 111:    */     {
/* 112:    */       public CachedValueProvider.Result<XmlElementDescriptor> compute(RngElementDescriptor paramAnonymousRngElementDescriptor)
/* 113:    */       {
/* 114:107 */         XmlElementDescriptor localXmlElementDescriptor = paramAnonymousRngElementDescriptor.findElementDescriptor(paramXmlTag1);
/* 115:108 */         return CachedValueProvider.Result.create(localXmlElementDescriptor, new Object[] { paramAnonymousRngElementDescriptor.getDependences(), paramXmlTag1 });
/* 116:    */       }
/* 117:110 */     });
/* 118:111 */     return localXmlElementDescriptor == NULL ? null : localXmlElementDescriptor;
/* 119:    */   }
/* 120:    */   
/* 121:    */   public final XmlAttributeDescriptor[] getAttributesDescriptors(@Nullable final XmlTag paramXmlTag)
/* 122:    */   {
/* 123:115 */     if (paramXmlTag != null) {
/* 124:116 */       (XmlAttributeDescriptor[])a(paramXmlTag, this, b, new ParameterizedCachedValueProvider()
/* 125:    */       {
/* 126:    */         public CachedValueProvider.Result<XmlAttributeDescriptor[]> compute(RngElementDescriptor paramAnonymousRngElementDescriptor)
/* 127:    */         {
/* 128:118 */           XmlAttributeDescriptor[] arrayOfXmlAttributeDescriptor = paramAnonymousRngElementDescriptor.collectAttributeDescriptors(paramXmlTag);
/* 129:119 */           return CachedValueProvider.Result.create(arrayOfXmlAttributeDescriptor, new Object[] { paramAnonymousRngElementDescriptor.getDependences(), paramXmlTag });
/* 130:    */         }
/* 131:    */       });
/* 132:    */     }
/* 133:123 */     return collectAttributeDescriptors(null);
/* 134:    */   }
/* 135:    */   
/* 136:    */   private static <D extends PsiElement, T, P> T a(D paramD, P paramP, Key<ParameterizedCachedValue<T, P>> paramKey, ParameterizedCachedValueProvider<T, P> paramParameterizedCachedValueProvider)
/* 137:    */   {
/* 138:128 */     CachedValuesManager localCachedValuesManager = CachedValuesManager.getManager(paramD.getProject());
/* 139:129 */     return localCachedValuesManager.getParameterizedCachedValue(paramD, paramKey, paramParameterizedCachedValueProvider, false, paramP);
/* 140:    */   }
/* 141:    */   
/* 142:    */   protected XmlAttributeDescriptor[] collectAttributeDescriptors(@Nullable XmlTag paramXmlTag)
/* 143:    */   {
/* 144:133 */     return computeAttributeDescriptors(AttributeFinder.find((QName)null, new DPattern[] { this.c }));
/* 145:    */   }
/* 146:    */   
/* 147:    */   protected XmlAttributeDescriptor[] computeAttributeDescriptors(Map<DAttributePattern, Pair<? extends Map<String, String>, Boolean>> paramMap)
/* 148:    */   {
/* 149:137 */     HashMap localHashMap = new HashMap();
/* 150:139 */     for (Object localObject1 = paramMap.keySet().iterator(); ((Iterator)localObject1).hasNext();)
/* 151:    */     {
/* 152:139 */       localDAttributePattern = (DAttributePattern)((Iterator)localObject1).next();
/* 153:140 */       localPair = (Pair)paramMap.get(localDAttributePattern);
/* 154:141 */       for (QName localQName : localDAttributePattern.getName().listNames())
/* 155:    */       {
/* 156:142 */         Object localObject2 = (RngXmlAttributeDescriptor)localHashMap.get(localQName);
/* 157:143 */         RngXmlAttributeDescriptor localRngXmlAttributeDescriptor = new RngXmlAttributeDescriptor(this, localDAttributePattern, (Map)localPair.first, ((Boolean)localPair.second).booleanValue());
/* 158:144 */         if (localObject2 == null) {
/* 159:145 */           localObject2 = localRngXmlAttributeDescriptor;
/* 160:    */         } else {
/* 161:148 */           localObject2 = ((RngXmlAttributeDescriptor)localObject2).mergeWith(localRngXmlAttributeDescriptor);
/* 162:    */         }
/* 163:150 */         localHashMap.put(localQName, localObject2);
/* 164:    */       }
/* 165:    */     }
/* 166:    */     DAttributePattern localDAttributePattern;
/* 167:    */     Pair localPair;
/* 168:154 */     localObject1 = localHashMap.values();
/* 169:155 */     return (XmlAttributeDescriptor[])((Collection)localObject1).toArray(new RngXmlAttributeDescriptor[((Collection)localObject1).size()]);
/* 170:    */   }
/* 171:    */   
/* 172:    */   public final XmlAttributeDescriptor getAttributeDescriptor(String paramString, @Nullable XmlTag paramXmlTag)
/* 173:    */   {
/* 174:159 */     return getAttributeDescriptor("", paramString);
/* 175:    */   }
/* 176:    */   
/* 177:    */   public final XmlAttributeDescriptor getAttributeDescriptor(XmlAttribute paramXmlAttribute)
/* 178:    */   {
/* 179:163 */     return getAttributeDescriptor(paramXmlAttribute.getNamespace(), paramXmlAttribute.getLocalName());
/* 180:    */   }
/* 181:    */   
/* 182:    */   protected XmlAttributeDescriptor getAttributeDescriptor(String paramString1, String paramString2)
/* 183:    */   {
/* 184:167 */     QName localQName = new QName(paramString1, paramString2);
/* 185:    */     
/* 186:169 */     return computeAttributeDescriptor(AttributeFinder.find(localQName, new DPattern[] { this.c }));
/* 187:    */   }
/* 188:    */   
/* 189:    */   protected XmlAttributeDescriptor computeAttributeDescriptor(Map<DAttributePattern, Pair<? extends Map<String, String>, Boolean>> paramMap)
/* 190:    */   {
/* 191:173 */     if (paramMap.size() > 0)
/* 192:    */     {
/* 193:174 */       Object localObject = null;
/* 194:175 */       Set localSet = paramMap.keySet();
/* 195:176 */       for (DAttributePattern localDAttributePattern : localSet)
/* 196:    */       {
/* 197:177 */         Pair localPair = (Pair)paramMap.get(localDAttributePattern);
/* 198:178 */         RngXmlAttributeDescriptor localRngXmlAttributeDescriptor = new RngXmlAttributeDescriptor(this, localDAttributePattern, (Map)localPair.first, ((Boolean)localPair.second).booleanValue());
/* 199:180 */         if (localObject == null) {
/* 200:181 */           localObject = localRngXmlAttributeDescriptor;
/* 201:    */         } else {
/* 202:183 */           localObject = ((RngXmlAttributeDescriptor)localObject).mergeWith(localRngXmlAttributeDescriptor);
/* 203:    */         }
/* 204:    */       }
/* 205:186 */       return localObject;
/* 206:    */     }
/* 207:188 */     return null;
/* 208:    */   }
/* 209:    */   
/* 210:    */   public XmlNSDescriptor getNSDescriptor()
/* 211:    */   {
/* 212:193 */     return this.myNsDescriptor;
/* 213:    */   }
/* 214:    */   
/* 215:    */   public XmlElementsGroup getTopGroup()
/* 216:    */   {
/* 217:198 */     return null;
/* 218:    */   }
/* 219:    */   
/* 220:    */   public int getContentType()
/* 221:    */   {
/* 222:203 */     DPattern localDPattern = this.c.getChild();
/* 223:204 */     if ((localDPattern instanceof DEmptyPattern)) {
/* 224:205 */       return 0;
/* 225:    */     }
/* 226:206 */     if ((localDPattern instanceof DTextPattern)) {
/* 227:207 */       return 3;
/* 228:    */     }
/* 229:208 */     if ((localDPattern instanceof DElementPattern)) {
/* 230:209 */       return ((Integer)((DElementPattern)localDPattern).getName().accept(MyNameClassVisitor.INSTANCE)).intValue();
/* 231:    */     }
/* 232:211 */     return 2;
/* 233:    */   }
/* 234:    */   
/* 235:    */   public String getDefaultValue()
/* 236:    */   {
/* 237:217 */     return null;
/* 238:    */   }
/* 239:    */   
/* 240:    */   public PsiElement getDeclaration()
/* 241:    */   {
/* 242:221 */     SmartPsiElementPointer localSmartPsiElementPointer = this.d;
/* 243:222 */     if (localSmartPsiElementPointer != null)
/* 244:    */     {
/* 245:223 */       localPsiElement1 = localSmartPsiElementPointer.getElement();
/* 246:224 */       if ((localPsiElement1 != null) && (localPsiElement1.isValid())) {
/* 247:225 */         return localPsiElement1;
/* 248:    */       }
/* 249:    */     }
/* 250:229 */     PsiElement localPsiElement1 = this.myNsDescriptor.getDeclaration();
/* 251:230 */     if (localPsiElement1 == null)
/* 252:    */     {
/* 253:231 */       this.d = null;
/* 254:232 */       return null;
/* 255:    */     }
/* 256:235 */     PsiElement localPsiElement2 = a(localPsiElement1, this.c.getLocation());
/* 257:236 */     if ((localPsiElement2 != null) && (localPsiElement2 != localPsiElement1)) {
/* 258:237 */       this.d = SmartPointerManager.getInstance(localPsiElement1.getProject()).createSmartPsiElementPointer(localPsiElement2);
/* 259:    */     }
/* 260:239 */     return localPsiElement2;
/* 261:    */   }
/* 262:    */   
/* 263:    */   public PsiElement getDeclaration(Locator paramLocator)
/* 264:    */   {
/* 265:243 */     PsiElement localPsiElement = this.myNsDescriptor.getDeclaration();
/* 266:244 */     if (localPsiElement == null) {
/* 267:245 */       return null;
/* 268:    */     }
/* 269:247 */     return a(localPsiElement, paramLocator);
/* 270:    */   }
/* 271:    */   
/* 272:    */   private static PsiElement a(PsiElement paramPsiElement, Locator paramLocator)
/* 273:    */   {
/* 274:251 */     VirtualFile localVirtualFile = RngSchemaValidator.findVirtualFile(paramLocator.getSystemId());
/* 275:252 */     if (localVirtualFile == null) {
/* 276:253 */       return paramPsiElement;
/* 277:    */     }
/* 278:256 */     Project localProject = paramPsiElement.getProject();
/* 279:257 */     PsiFile localPsiFile = PsiManager.getInstance(localProject).findFile(localVirtualFile);
/* 280:258 */     if (localPsiFile == null) {
/* 281:259 */       return paramPsiElement;
/* 282:    */     }
/* 283:262 */     int i = paramLocator.getColumnNumber();
/* 284:263 */     int j = paramLocator.getLineNumber();
/* 285:    */     
/* 286:265 */     Document localDocument = PsiDocumentManager.getInstance(localProject).getDocument(localPsiFile);
/* 287:266 */     assert (localDocument != null);
/* 288:268 */     if ((j <= 0) || (localDocument.getLineCount() < j - 1)) {
/* 289:269 */       return paramPsiElement;
/* 290:    */     }
/* 291:271 */     int k = localDocument.getLineStartOffset(j - 1);
/* 292:    */     PsiElement localPsiElement2;
/* 293:    */     PsiElement localPsiElement1;
/* 294:274 */     if (i > 0)
/* 295:    */     {
/* 296:275 */       if (paramPsiElement.getContainingFile().getFileType() == RncFileType.getInstance())
/* 297:    */       {
/* 298:276 */         localPsiElement2 = localPsiFile.findElementAt(k + i);
/* 299:277 */         Object localObject1 = localPsiElement2 != null ? TreeUtil.findParent(localPsiElement2.getNode(), RncElementTypes.PATTERN) : null;
/* 300:278 */         Object localObject2 = localObject1 != null ? localObject1.findChildByType(RncElementTypes.NAME_CLASS) : null;
/* 301:279 */         return localObject2 != null ? localObject2.getPsi() : localPsiElement2;
/* 302:    */       }
/* 303:281 */       localPsiElement1 = localPsiFile.findElementAt(k + i - 2);
/* 304:    */     }
/* 305:    */     else
/* 306:    */     {
/* 307:283 */       localPsiElement2 = localPsiFile.findElementAt(k);
/* 308:284 */       localPsiElement1 = localPsiElement2 != null ? PsiTreeUtil.nextLeaf(localPsiElement2) : null;
/* 309:    */     }
/* 310:287 */     return PsiTreeUtil.getParentOfType(localPsiElement1, XmlTag.class);
/* 311:    */   }
/* 312:    */   
/* 313:    */   @NonNls
/* 314:    */   public String getName(PsiElement paramPsiElement)
/* 315:    */   {
/* 316:292 */     QName localQName = a();
/* 317:293 */     if (localQName == null) {
/* 318:294 */       return "#unknown";
/* 319:    */     }
/* 320:296 */     XmlTag localXmlTag = (XmlTag)PsiTreeUtil.getParentOfType(paramPsiElement, XmlTag.class, false);
/* 321:297 */     Object localObject = localXmlTag != null ? localXmlTag.getPrefixByNamespace(localQName.getNamespaceURI()) : null;
/* 322:298 */     return a(localQName, localObject != null ? localObject : localQName.getPrefix());
/* 323:    */   }
/* 324:    */   
/* 325:    */   @NonNls
/* 326:    */   public String getName()
/* 327:    */   {
/* 328:303 */     QName localQName = a();
/* 329:304 */     if (localQName == null) {
/* 330:305 */       return "#unknown";
/* 331:    */     }
/* 332:307 */     return localQName.getLocalPart();
/* 333:    */   }
/* 334:    */   
/* 335:    */   private static String a(QName paramQName, String paramString)
/* 336:    */   {
/* 337:311 */     String str = paramQName.getLocalPart();
/* 338:312 */     return paramString.length() > 0 ? paramString + ":" + str : str;
/* 339:    */   }
/* 340:    */   
/* 341:    */   @Nullable
/* 342:    */   private QName a()
/* 343:    */   {
/* 344:317 */     Iterator localIterator = this.c.getName().listNames().iterator();
/* 345:318 */     if (!localIterator.hasNext()) {
/* 346:319 */       return null;
/* 347:    */     }
/* 348:321 */     return (QName)localIterator.next();
/* 349:    */   }
/* 350:    */   
/* 351:    */   public void init(PsiElement paramPsiElement) {}
/* 352:    */   
/* 353:    */   public boolean equals(Object paramObject)
/* 354:    */   {
/* 355:329 */     if (this == paramObject) {
/* 356:329 */       return true;
/* 357:    */     }
/* 358:330 */     if ((paramObject == null) || (getClass() != paramObject.getClass())) {
/* 359:330 */       return false;
/* 360:    */     }
/* 361:332 */     RngElementDescriptor localRngElementDescriptor = (RngElementDescriptor)paramObject;
/* 362:334 */     if (!this.c.equals(localRngElementDescriptor.c)) {
/* 363:334 */       return false;
/* 364:    */     }
/* 365:336 */     return true;
/* 366:    */   }
/* 367:    */   
/* 368:    */   public int hashCode()
/* 369:    */   {
/* 370:340 */     return this.c.hashCode();
/* 371:    */   }
/* 372:    */   
/* 373:    */   public Object[] getDependences()
/* 374:    */   {
/* 375:344 */     if (this.d != null) {
/* 376:345 */       return ArrayUtil.append(this.myNsDescriptor.getDependences(), this.d.getElement());
/* 377:    */     }
/* 378:347 */     return this.myNsDescriptor.getDependences();
/* 379:    */   }
/* 380:    */   
/* 381:    */   private static class MyNameClassVisitor
/* 382:    */     implements NameClassVisitor<Integer>
/* 383:    */   {
/* 384:352 */     public static final MyNameClassVisitor INSTANCE = new MyNameClassVisitor();
/* 385:    */     
/* 386:    */     public Integer visitAnyName()
/* 387:    */     {
/* 388:355 */       return Integer.valueOf(1);
/* 389:    */     }
/* 390:    */     
/* 391:    */     public Integer visitAnyNameExcept(NameClass paramNameClass)
/* 392:    */     {
/* 393:359 */       return Integer.valueOf(1);
/* 394:    */     }
/* 395:    */     
/* 396:    */     public Integer visitChoice(NameClass paramNameClass1, NameClass paramNameClass2)
/* 397:    */     {
/* 398:363 */       return Integer.valueOf(2);
/* 399:    */     }
/* 400:    */     
/* 401:    */     public Integer visitName(QName paramQName)
/* 402:    */     {
/* 403:367 */       return Integer.valueOf(2);
/* 404:    */     }
/* 405:    */     
/* 406:    */     public Integer visitNsName(String paramString)
/* 407:    */     {
/* 408:371 */       return Integer.valueOf(2);
/* 409:    */     }
/* 410:    */     
/* 411:    */     public Integer visitNsNameExcept(String paramString, NameClass paramNameClass)
/* 412:    */     {
/* 413:375 */       return Integer.valueOf(2);
/* 414:    */     }
/* 415:    */     
/* 416:    */     public Integer visitNull()
/* 417:    */     {
/* 418:379 */       return Integer.valueOf(0);
/* 419:    */     }
/* 420:    */   }
/* 421:    */   
/* 422:    */   public DElementPattern getElementPattern()
/* 423:    */   {
/* 424:384 */     return this.c;
/* 425:    */   }
/* 426:    */ }



/* Location:           E:\idea\

 * Qualified Name:     org.intellij.plugins.relaxNG.model.descriptors.RngElementDescriptor

 * JD-Core Version:    0.7.0.1

 */